import {
  Entity,
  PrimaryGeneratedColumn,
  Column,
  Index,
  CreateDateColumn,
  UpdateDateColumn,
  OneToMany,
  ManyToMany,
  DeleteDateColumn,
} from 'typeorm';
import {
  IsOptional,
  IsNotEmpty,
  IsString,
  MaxLength,
  IsBoolean,
  IsNumber,
  IsISO8601,
} from 'class-validator';
import { Type } from 'class-transformer';
import { CrudValidationGroups } from '@nestjsx/crud';
import { User } from '@/modules/users/entities/user.entity';
import { Artist } from './artist.entity';
import { Song } from './song.entity';
import { AlbumEdition } from './album-edition.entity';

const { CREATE, UPDATE } = CrudValidationGroups;

@Entity({ name: 'albums' })
export class Album {
  @IsOptional({ always: true })
  @PrimaryGeneratedColumn()
  id: number;

  @Type(_type => Artist)
  @ManyToMany(
    _type => Artist,
    artist => artist.hasAlbums,
  )
  belongsToArtists: Artist[];

  @Type(_type => Artist)
  @ManyToMany(
    _type => Artist,
    artist => artist.hasProducedAlbums,
  )
  hasProducers: Artist[];

  @Type(_type => Song)
  @OneToMany(
    _type => Song,
    song => song.belongsToAlbum,
  )
  hasSongs: Song[];

  @Type(_type => AlbumEdition)
  @OneToMany(
    _type => AlbumEdition,
    edition => edition.album,
  )
  editions: AlbumEdition[];

  @Type(_type => User)
  @ManyToMany(
    _type => User,
    user => user.favAlbums,
  )
  favByUsers: User[];

  @IsOptional({ always: true })
  @IsNumber({}, { always: true })
  @Column({ type: 'int', default: 0, comment: '喜欢量' })
  favCount: number;

  @IsOptional({ groups: [UPDATE] })
  @IsNotEmpty({ groups: [CREATE] })
  @IsString({ always: true })
  @MaxLength(200, { always: true })
  @Index()
  @Column({ type: 'character varying', length: 200, comment: '专辑名' })
  title: string;

  @IsOptional({ always: true })
  @IsString({ always: true })
  @Column({ type: 'text', nullable: true, comment: '详细信息' })
  description: string;

  @IsOptional({ always: true })
  @IsString({ always: true })
  @MaxLength(100, { always: true })
  @Column({
    type: 'character varying',
    length: 100,
    nullable: true,
    comment: '封面图片',
  })
  coverImage: string;

  @IsOptional({ groups: [UPDATE] })
  @IsNotEmpty({ groups: [CREATE] })
  @IsString({ always: true })
  @MaxLength(60)
  @Index()
  @Column({
    type: 'character varying',
    length: 60,
    nullable: true,
    comment: '唱片厂牌',
  })
  recordLabel: string;

  @IsOptional({ groups: [UPDATE] })
  @IsNotEmpty({ groups: [CREATE] })
  @IsISO8601({}, { always: true })
  @Column({ type: 'date', nullable: true, comment: '发行日期' })
  publishDate: Date;

  @IsOptional({ always: true })
  @IsString({ each: true, always: true })
  @MaxLength(20, { each: true, always: true })
  @Column({
    type: 'character varying',
    length: 20,
    array: true,
    nullable: true,
    comment: '类型标签',
  })
  types: string[];

  @IsOptional({ always: true })
  @IsBoolean({ always: true })
  @Column({ type: 'boolean', default: true, comment: '是否可见' })
  visible = true;

  @CreateDateColumn()
  createdAt: Date;

  @UpdateDateColumn()
  updatedAt: Date;

  @DeleteDateColumn()
  deletedAt: Date;
}
